#pragma once
#include <iostream>
#include <memory>
#include <fstream>
#include <sstream>
#include <sys/types.h>
#include <sys/stat.h>
#include <filesystem>


namespace Cloude
{
	using std::string;
	using std::vector;
	using std::endl;
	using std::cout;
	using std::ios;
	namespace fs = std::filesystem;

	class FileUtil
	{
	private: 
		string _filename;
	public:
		FileUtil(string filename)
			:_filename(filename)
		{}

		// 获取文件名
		// /download/a.txt --> a.txt
		string FileName()
		{
			// windows中路径分隔符是不同的！
			auto pos = _filename.rfind("\\");
			string sub = _filename.substr(pos+1,string::npos);
			return sub;
		}
		// 删除文件
		bool RemoveFile()
		{
			if(remove(_filename.c_str()) == -1)
			{
				cout << "FileUtil::RemoveFile failed.." << endl;
				printf("%d-%s\n",errno,strerror(errno));
				return false;
			}
			return true;
		}


		// ofs,ifs,中的read,write类型都是char* ,c_str() 是const char*
		// 所以不能c_str 作为参数，存在权限放大

		// 获取文件数据 - 读 - 读到内存中 in
		bool GetContent(string* str)
		{
			std::ifstream ifs;
			ifs.open(_filename,ios::in | ios::binary);
			if(ifs.is_open() == false)
			{
				cout << "FileUtil::GetContent,open failed.." << endl;
				printf("%d-%s %s\n",errno,strerror(errno),_filename.c_str());
				return false;
			}
			size_t sz = GetFileSize();
			str->resize(sz);
			ifs.read( &( (*str) [0] ) ,sz);
			if(ifs.good() == false)
			{	
				cout << "FileUtil::GetContent,good failed.." << endl;
				printf("%d-%s\n",errno,strerror(errno));
				return false;
			}
			return true;
		}
		// 保存文件数据 - 写 - 写到文件中
		bool SetContent(const string& str)
		{
			std::ofstream ofs;
			ofs.open(_filename, ios::out | ios::binary);
			if(ofs.is_open() == false)
			{
				cout << "FileUtil::SetContent,open failed.." << endl;
				printf("%d-%s %s\n",errno,strerror(errno),_filename.c_str());
				ofs.close();
				return false;
			}
			size_t sz = str.size();
			ofs.write(&str[0],sz);
			if(ofs.good() == false)
			{
				cout << "FileUtil::SetContent,good failed.." << endl;
				printf("%d-%s\n",errno,strerror(errno));
				ofs.close();
				return false;
			}
			ofs.close();
			return true;
		}
		// 获取文件大小
		size_t GetFileSize()
		{
			struct stat st;
			stat(_filename.c_str(),&st);
			return st.st_size;
		}

		// 获取最近一次访问时间
		time_t GetATime()
		{
			struct stat st;
			stat(_filename.c_str(),&st);
			return st.st_atime;

		}
		// 获取最近一次修改时间
		time_t GetMTime()
		{
			struct stat st;
			stat(_filename.c_str(),&st);
			return st.st_mtime;

		}

		// 判断文件/目录是否存在
		bool IsExist()
		{
			return	fs::exists(_filename);
		}

		// 创建目录
		bool CreateDirectorY()
		{
			if(IsExist() == true)
			{
				return true;
			}
			return fs::create_directory(_filename);
		}

		// 获取目录下的所有文件名
		bool ScanDirectory(vector<string>* arry)
		{
			if(IsExist() == false)
			{
				cout << "FileUtil::ScanDir failed..." << endl;
				return false;
			}
	
			for (auto& entry : fs::directory_iterator(_filename))
			{
				// 带有路径的文件名
				arry->push_back(entry.path().relative_path().string());
			}
			return true;
		}

	};
}